package controllers

import (
	"strconv"
	"time"
	"web_app/logic"
	"web_app/models"

	"github.com/go-playground/validator/v10"

	"go.uber.org/zap"

	"github.com/gin-gonic/gin"
)

// CreatePost 添加帖子详情
func CreatePost(c *gin.Context) {
	post := &models.Post{}
	if err := c.ShouldBindJSON(post); err != nil {
		zap.L().Error("ShouldBindJSON failed", zap.Error(err))
		ResponseError(c, CodeInvalidParam)
		return
	}
	post.CreateTime = time.Now()
	authorId, err := GetCurrentUserID(c)
	if err != nil {
		ResponseError(c, CodeNeedAuth)
		return
	}
	post.AuthorId = authorId
	if err := logic.CreatePost(post); err != nil {
		ResponseError(c, CodeServerBusy)
		return
	}
	ResponseSuccess(c, post)
}

// GetPostDetailByID 根据帖子id获取帖子详情
func GetPostDetailByID(c *gin.Context) {
	strID := c.Param("id")
	id, err := strconv.ParseInt(strID, 10, 64)
	if err != nil {
		ResponseError(c, CodeInvalidParam)
		return
	}
	postDetail, err := logic.GetPostDetailByID(id)
	if err != nil {
		zap.L().Error("logic.GetPostDetailByID(id) failed", zap.Error(err))
		ResponseError(c, CodeServerBusy)
		return
	}
	ResponseSuccess(c, postDetail)
}

// GetPostList 获取帖子分页列表
func GetPostList(c *gin.Context) {
	//获取分页数据
	var err error
	page := new(models.Page)
	postList := make([]*models.ApiPostDetail, 0)
	page.PageSize, err = strconv.ParseInt(c.Query("page_size"), 10, 64)
	if err != nil {
		page.PageSize = 0
	}
	page.PageCount, err = strconv.ParseInt(c.Query("page_count"), 10, 64)
	if err != nil {
		page.PageCount = 0
	}
	//查询列表
	postList, err = logic.GetPostList(page)
	if err != nil {
		ResponseError(c, CodeServerBusy)
		return
	}
	ResponseSuccess(c, postList)
}

// GetPostListInOrder 根据时间或者分数对帖子列表进行排序
// GetPostListInOrder 升级版帖子列表接口
// @Summary 升级版帖子列表接口
// @Description 可按社区按时间或分数排序查询帖子列表接口
// @Tags 帖子相关接口
// @Accept application/json
// @Produce application/json
// @Param Authorization header string true "Bearer JWT"
// @Param object query models.ParamsPostInOrder false "查询参数"
// @Security ApiKeyAuth
// @Success 200 {object} _ResponsePostList
// @Router /postV2 [get]
func GetPostListInOrder(c *gin.Context) {
	//1.获取参数验证参数
	p := new(models.ParamsPostInOrder)
	if err := c.ShouldBind(p); err != nil {
		ResponseError(c, CodeInvalidParam)
		return
	}
	//2.根据参数获取数据
	data, err := logic.GetPostListInOrder(p)
	if err != nil {
		ResponseError(c, CodeServerBusy)
		return
	}
	//3.返回帖子列表
	ResponseSuccess(c, data)
}

// VoteForPost 为帖子投票的函数
func VoteForPost(c *gin.Context) {
	//1.获取帖子id以及用户id以及参数校验
	var err error
	paramsVoteData := new(models.ParamsVoteData)
	if err = c.ShouldBind(paramsVoteData); err != nil {
		errs, ok := err.(validator.ValidationErrors)
		if !ok {
			zap.L().Error("ShouldBind failed", zap.Error(err))
			ResponseError(c, CodeInvalidParam)
			return
		}
		ResponseErrorWithMsg(c, CodeInvalidParam, removeTopStruct(errs.Translate(trans)))
		return
	}
	paramsVoteData.UserID, err = GetCurrentUserID(c)
	if err != nil {
		ResponseError(c, CodeInvalidToken)
		return
	}
	//2处理投票逻辑
	err = logic.VoteForPost(paramsVoteData)
	if err != nil {
		zap.L().Error("logic.VoteForPost failed", zap.Error(err))
		ResponseError(c, CodeServerBusy)
		return
	}
	//3.返回处理结果
	ResponseSuccess(c, nil)
}
